<template>
  <div class="flex-one">
    <a-upload
      v-bind="$props"
      :multiple="true"
      :action="url"
      list-type="picture-card"
      :beforeUpload="beforeUpload"
      :headers="{
        tokenSign: tokenSign,
        userId,
        Authorization: token,
        token: token,
        accountId
      }"
      v-model:file-list="fileList"
      @change="change"
      @preview="handlePreview"
    >
      <div v-if="fileList.length < limitNum">
        <plus-outlined />
        <div class="ant-upload-text">Upload</div>
      </div>
    </a-upload>
    <a-modal :visible="previewVisible" :footer="null" @cancel="handleCancel">
      <a-button class="mb10" @click="fetchImg(previewImage)" type="primary"
        >下载</a-button
      >
      <img
        alt="该文件不支持在线查看，可尝试下载下来查看"
        style="width: 100%"
        :src="previewImage"
      />
    </a-modal>
  </div>
</template>
<script>
import { PlusOutlined } from '@ant-design/icons-vue'
import { defineComponent, ref, watch } from 'vue'
import { message } from 'ant-design-vue'
import axios from 'axios'
const uploadURL = process.env.VUE_APP_ERP_IMG
import { getQueryString } from 'cupshe-utils'

function getBase64(file) {
  return new Promise((resolve, reject) => {
    const reader = new FileReader()
    reader.readAsDataURL(file)
    reader.onload = () => resolve(reader.result)
    reader.onerror = error => reject(error)
  })
}
export default defineComponent({
  components: {
    PlusOutlined
  },
  props: {
    disabled: {
      type: Boolean,
      default: false
    },
    imgList: {
      type: Array,
      default: () => []
    },
    img: {
      type: String,
      default: ''
    },
    accept: {
      type: String,
      default: ''
    },
    limitNum: {
      type: Number,
      default: 30
    },
    size: {
      type: Number,
      default: 3
    }
  },
  emits: ['update:imgList', 'change', 'update:img'],
  setup(props, { emit }) {
    const previewVisible = ref(false)
    const previewImage = ref('')
    const url = ref(uploadURL)
    let count = 0
    const token = ref(localStorage.token)
    const userId = ref(localStorage.userId)
    const accountId = ref(localStorage.accountId)
    const fileList = ref([])
    watch(
      () => props.imgList,
      newValue => {
        fileList.value = []
        newValue.forEach(_ => {
          ++count
          const obj = { ..._ }
          _.ossUrl && (obj.url = _.ossUrl)
          _.ossUrl && (obj.name = _.ossname)
          obj.uid = _.id || count
          fileList.value.push(obj)
        })
        // emit('change', fileList.value)
      },
      {
        deep: true,
        immediate: true
      }
    )
    watch(
      () => props.img,
      newValue => {
        if (fileList.value.length === 0 && newValue) {
          fileList.value.push({
            name: '图片',
            ossName: '图片',
            ossUrl: newValue,
            url: newValue,
            uid: Math.random()
          })
        }
        // emit('change', fileList.value)
      },
      { immediate: true }
    )
    const handleCancel = () => {
      previewVisible.value = false
    }
    const beforeUpload = file => {
      const isLt2M = file.size / 1024 / 1024 < props.size
      if (!isLt2M) {
        message.error(`File must smaller than ${props.size}MB!`)
      }
      return new Promise((resolve, reject) => {
        return isLt2M ? resolve(isLt2M) : reject(isLt2M)
      })
    }
    const change = val => {
      if (val.file.status === 'done' || val.file.status === 'removed') {
        /*
         * 组装成PLM项目需要的数据格式
         */
        const images = []
        val.fileList.forEach(_ => {
          const uid = Math.random()
          _.uid = _.uid || uid
          if (_.response && _.response.data) {
            const { ossAlias, ossName, ossSuffix, ossUrl } = _.response.data
            images.push({
              uid,
              ossAlias,
              ossName,
              ossSuffix,
              ossUrl,
              name: ossName,
              url: ossUrl
            })
          } else {
            _.ossUrl = _.url
            _.ossName = _.name
            images.push(_)
          }
        })

        emit('update:imgList', images)
        emit('update:img', images[0] ? images[0].ossUrl : '')
        emit('change', images)
      }
      if (val.file.status === 'error') {
        message.error('upload error')
      }
    }
    const handlePreview = async file => {
      if (!file.url && !file.preview) {
        file.preview = await getBase64(file.originFileObj)
      }

      previewImage.value = file.url || file.preview
      previewVisible.value = true
    }

    const handleChange = ({ fileList: newFileList }) => {
      fileList.value = newFileList
    }
    const fetchImg = async (img, name = '下载', errorInfo = '导出失败') => {
      if (
        img.endsWith('ai') ||
        img.endsWith('pdf') ||
        img.endsWith('prj') ||
        img.endsWith('webp') ||
        img.endsWith('psd') ||
        img.endsWith('dxf') ||
        img.endsWith('rul') ||
        img.endsWith('xlsx') ||
        img.endsWith('excel')
      ) {
        // window.open(img)
        const a = document.createElement('a')
        a.setAttribute('href', img)
        a.setAttribute('target', '_blank')
        a.setAttribute('download', '')
        a.click()
        return
      }
      try {
        const response = await axios({
          methods: 'get',
          headers: {
            'Content-Type': 'multipart/form-data',
            token: localStorage.userId,
            accountId: localStorage.accountId
          },
          url: img.replace('https:', window.location.protocol),
          responseType: 'blob'
        })
        const blob = await new Blob([response.data], { type: 'image/png' })
        // 创建隐藏的可下载链接
        const objectUrl = window.URL.createObjectURL(blob)
        const a = document.createElement('a')
        // 地址
        a.href = objectUrl
        // 修改文件名
        a.download = name
        // 触发点击
        document.body.appendChild(a)
        a.click()
        // 移除
        window.URL.revokeObjectURL(blob)
        setTimeout(() => document.body.removeChild(a), 1000)
      } catch (error) {
        message.error(errorInfo)
      }
    }
    return {
      fetchImg,
      previewVisible,
      previewImage,
      fileList,
      handleCancel,
      handlePreview,
      handleChange,
      tokenSign: getQueryString('tokensign') || 2,
      token,
      userId,
      url,
      accountId,
      change,
      beforeUpload
    }
  }
})
</script>
<style>
/* you can make up upload button and sample style by using stylesheets */
.ant-upload-select-picture-card i {
  font-size: 32px;
  color: #999;
}
.ant-upload-select-picture-card .ant-upload-text {
  margin-top: 8px;
  color: #666;
}
.flex-one {
  flex: 1;
}
</style>
